#ifndef DATACENTER_H
#define DATACENTER_H

#include <QWidget>
#include <QStandardPaths>
#include <QDir>
#include <QJsonObject>
#include <QJsonDocument>

#include "../network/netclient.h"
#include "data.h"
namespace model
{
    class DataCenter : public QObject
    {
        Q_OBJECT

    public:
        static DataCenter *getInstance();
        ~DataCenter();

        // 初始化数据文件
        void initDataFile();
        // 存储数据到文件中
        void saveDataFile();
        // 加载文件数据
        void loadDataFile();
        // 清空未读消息数目
        void clearUnread(const QString &chatSessionId);
        // 增加未读消息数目
        void addUnread(const QString &chatSessionId);
        // 获取未读消息数目
        int getUnread(const QString &chatSessionId);

        // 获取到当前会话登录id
        const QString &getLoginSessionId() const { return _loginSessionId; }
        const QString &getCurrentSessionId() const { return _currentChatSessionId; }

        void ping() { _netClient->ping(); }

        ///////////////////////////////////
        /// 核心函数
        ///////////////////////////////////
        // 获取个人信息
        void getMyselfAsync();
        UserInfo* getMyself() { return _myself; }
        void resetMyself(std::shared_ptr<LYZ::GetUserInfoRsp> rsp);

        // 获取好友列表
        void getFriendListAsync();
        QList<UserInfo> *getFriendList() { return _friendList; }
        void resetFriendList(std::shared_ptr<LYZ::GetFriendListRsp> rsp);

        // 获取会话列表
        void getChatSessionListAsync();
        QList<ChatSessionInfo> *getChatSessionList() { return _chatSessionList; }
        void resetChatSessionList(std::shared_ptr<LYZ::GetChatSessionListRsp> rsp);

        // 获取申请列表
        void getApplyListAsync();
        QList<UserInfo> *getApplyList() { return _applyList; }
        void resetApplyList(std::shared_ptr<LYZ::GetPendingFriendEventListRsp > rsp);

        // 获取会话最近消息
        void getRecentMsgAsync(const QString &chatSessionId, bool updateUI = true);
        QList<MessageInfo> *getRecentMsg(const QString &chatSessionId);
        void resetRecentMsgList(const QString &chatSessionId, std::shared_ptr<LYZ::GetRecentMsgRsp> rsp);

        // 发送消息给服务器
        void sentTextMessageAsync(const QString &chatSessionId, const QString &content);

        // 修改用户昵称
        void changeNicknameAsync(const QString &newName);
        void resetNickname(const QString &newName);

        ///////////////////////////////////
        /// 辅助函数
        ///////////////////////////////////
        // 通过id查询会话信息
        ChatSessionInfo *findChatSessionById(const QString &chatSessionId);
        // 通过用户id查询会话信息
        ChatSessionInfo *findChatSessionByUserId(const QString &userId);
        // 置顶会话信息
        void topChatSessionInfo(const ChatSessionInfo &chatSessionInfo);

        // 设置/获取当前会话id
        void setCurrentChatSessionId(const QString &chatSessionId) { _currentChatSessionId = chatSessionId; }
        QString setCurrentChatSessionId() { return _currentChatSessionId; }

        // 添加消息到dataCenter中
        void addMessage(MessageInfo msg);

        // 更新会话最后一条消息
        void updateChatSessionLastMsg(const QString &chatSessionId, const MessageInfo &msgInfo);

    private:
        DataCenter();

        static DataCenter *instance;

        // 登录会话id
        QString _loginSessionId = "";

        // 当前用户信息
        UserInfo *_myself = nullptr;

        // 当前用户好友列表
        QList<UserInfo> *_friendList = nullptr;

        // 当前用户会话列表
        QList<ChatSessionInfo> *_chatSessionList = nullptr;

        // 当前选中的会话
        QString _currentChatSessionId = "";

        // 记录每个会话中都有哪些成员(主要针对群聊)
        QHash<QString, QList<UserInfo>> *_memberList = nullptr;

        // 待处理的好友申请列表
        QList<UserInfo> *_applyList = nullptr;

        // 每个会话的最近消息列表
        QHash<QString, QList<MessageInfo>> *_recentMessages = nullptr;

        // 存储每个会话未读消息的个数
        QHash<QString, int> *_unreadMessageCount = nullptr;

        // 用户的好友搜索结果
        QList<UserInfo> *_searchUserResult = nullptr;

        // 历史消息搜索结果
        QList<MessageInfo> *_searchMessageResult = nullptr;

        // 邮件验证码的id
        QString _verifyCodeId = "";

        // 让dataCenter 持有 NetClient 模块
        network::NetClient *_netClient;
    signals:
        void getMyselfDone();
        void getFriendListDone();
        void getChatSessionListDone();
        void getApplyListDone();
        void getRecentMsgDone(const QString &chatSessionId);
        void getRecentMsgNoUiDone(const QString &chatSessionId, const model::MessageInfo &message);
        void sendMessageDone(MessageType msgType, const QByteArray &content, const QString &extraInfo);
        void updateLastMsg(const QString &chatSessionId);
        void receiveMessageDone(const model::MessageInfo &message);
        void changeNicknameDone();
    };
}

#endif // DATACENTER_H
